from PyPDF2 import PdfReader, PdfWriter
from pdf2docx import Converter
from docx2pdf import convert
from PyQt5.QtCore import QThread, pyqtSignal
import os


def getPageNum(filePath):
    """
    根据路径获取PDF的页数
    """
    try:
        file = PdfReader(filePath)
    except FileNotFoundError:
        return
    return str(len(file.pages))


def changeSuffix2PDF(path):
    """
    将路径末尾的.doc后缀或者.docx后缀更改为.pdf
    """
    if path[-4:] == ".doc":
        return path[:-4] + ".pdf"
    elif path[-5:] == ".docx":
        return path[:-5] + ".pdf"
    else:
        return None


def toPDF(sourcePath, targetPath):
    """
    目前仅支持win、mac系统, 且需要安装Microsoft Word
    """
    convert(sourcePath, targetPath)


def toWord(sourcePath, targetPath):
    c = Converter(sourcePath)
    c.convert(targetPath)


def getIndexFromString(inputStr):
    """
    将选取页码的字符串转换成列表, 包含需要选中的页码(从0开始, -1表示空白页)
    示例输入: "1-3, 5, ,9"
    示例输出: [0, 1, 2, 4, -1, 8]
    """
    newStr = inputStr.replace(" ", "")
    newStr = newStr.replace("，", ",")
    requirePagesIndex = []    # 从0开始，可直接使用get方法
    for item in newStr.split(','):
        if len(item) == 0:
            # 空白页
            requirePagesIndex.append(-1)    # 表示空白页
        elif item.find('-') == -1:
            # 不带范围的页码，不包含-字符
            requirePagesIndex.append(int(item) - 1)
        else:
            start, end = item.split("-")
            for i in [page for page in range(int(start), int(end) + 1)]:
                requirePagesIndex.append(i - 1)
    return requirePagesIndex


def extractPDF(file, pages, targetPath):
    """
    从PDF中提取选中的页数保存到tagetPath
    file: 文件的完整路径
    pages: 页码的字符串(示例: 2,3-5,7-9)
    targetPath: 保存的路径(包含文件名)
    """
    reader = PdfReader(file)
    writer = PdfWriter()
    index = getIndexFromString(pages)
    # 根据第一页获取pdf文件的尺寸
    firstPage = reader.pages[0]
    for pageIndex in index:
        if pageIndex == -1:
            writer.add_blank_page(firstPage.mediabox.width, firstPage.mediabox.height)
            continue
        obj = reader.pages[pageIndex]
        writer.add_page(obj)
    writer.write(open(targetPath, 'wb'))


class Word2PDFThread(QThread):
    transStatus = pyqtSignal(int)
    def __init__(self, files, exportPath):
        super(Word2PDFThread, self).__init__()
        self.files = files
        self.exportPath = exportPath
    
    def run(self):
        if self.files == []:
            return
        if self.exportPath == "":
            # 输出到原目录
            num = int(0)
            for file in self.files:
                toPDF(file, changeSuffix2PDF(file))
                num += 1
                self.transStatus.emit(num)
        else:
            # 指定了输出目录
            num = int(0)
            for file in self.files:
                toPDF(file, os.path.join(self.exportPath, changeSuffix2PDF(os.path.basename(file))))
                num += 1
                self.transStatus.emit(num)


class PDF2WordThread(QThread):
    transStatus = pyqtSignal(int)
    def __init__(self, files, exportPath):
        super(PDF2WordThread, self).__init__()
        self.files = files
        self.exportPath = exportPath
    
    def run(self):
        if self.files == []:
            return
        if self.exportPath == "":
            # 输出到原目录
            num = int(0)
            for file in self.files:
                toWord(file, file[:-4] + ".docx")
                num += 1
                self.transStatus.emit(num)
        else:
            # 指定了输出目录
            num = int(0)
            for file in self.files:
                toWord(file, os.path.join(self.exportPath, os.path.basename(file)[:-4] + ".docx"))
                num += 1
                self.transStatus.emit(num)


class PDFExtractThread(QThread):
    transStatus = pyqtSignal(int)
    def __init__(self, files, pages, exportPath):
        super(PDFExtractThread, self).__init__()
        self.files = files
        self.pages = pages
        self.exportPath = exportPath
    
    def run(self):
        if self.files == []:
            return
        if self.exportPath == "":
            # 输出到原目录
            num = int(0)
            for i in range(len(self.files)):
                extractPDF(self.files[i], self.pages[i], self.files[i][:-4] + "_提取.pdf")
                num += 1
                self.transStatus.emit(num)
        else:
            # 指定了输出目录
            num = int(0)
            for i in range(len(self.files)):
                extractPDF(self.files[i], self.pages[i], os.path.join(self.exportPath, os.path.basename(self.files[i])[:-4] + "_提取.pdf"))
                num += 1
                self.transStatus.emit(num)


class PDFMerge(QThread):
    transStatus = pyqtSignal(int)
    def __init__(self, files, exportPath, fileName):
        super(PDFMerge, self).__init__()
        self.files = files
        self.exportPath = exportPath
        self.fileName = fileName
    
    def run(self):
        if self.files == []:
            return
        if self.exportPath == "":
            # 输出到原目录(第一个文件的目录), 或者选了指定目录但没有指定
            catalogue = os.path.dirname(self.files[0])
            num = int(0)
            merger = PdfWriter()
            for pdf in self.files:
                merger.append(pdf)
                num += 1
                self.transStatus.emit(num)
            merger.write(os.path.join(catalogue, self.fileName))
            merger.close()
        else:
            # 指定了输出目录
            num = int(0)
            merger = PdfWriter()
            for pdf in self.files:
                merger.append(pdf)
                num += 1
                self.transStatus.emit(num)
            merger.write(os.path.join(self.exportPath, self.fileName))
            merger.close()
